import requests
import json
import time
import os
import sys
from datetime import datetime
##cron: */30 * * * *
##new Env("Hotcoin")
class WeComBot:
    """企业微信应用消息推送"""
    
    def __init__(self, corpid, corpsecret, agentid):
        self.corpid = corpid
        self.corpsecret = corpsecret
        self.agentid = agentid
        self.access_token = None
        self.token_expire_time = 0
    
    def get_access_token(self):
        """获取企业微信访问令牌"""
        # 如果令牌还有至少5分钟有效期，直接返回
        if self.access_token and time.time() < self.token_expire_time - 300:
            return self.access_token
        
        url = f"https://qyapi.weixin.qq.com/cgi-bin/gettoken?corpid={self.corpid}&corpsecret={self.corpsecret}"
        
        try:
            response = requests.get(url, timeout=10)
            response.raise_for_status()
            data = response.json()
            
            if data.get("errcode") == 0:
                self.access_token = data["access_token"]
                self.token_expire_time = time.time() + data["expires_in"]
                return self.access_token
            else:
                print(f"获取企业微信访问令牌失败: {data.get('errmsg')}")
                return None
                
        except Exception as e:
            print(f"获取企业微信访问令牌时发生错误: {e}")
            return None
    
    def send_message(self, content, msgtype="text"):
        """发送消息到企业微信应用"""
        token = self.get_access_token()
        if not token:
            return False
        
        url = f"https://qyapi.weixin.qq.com/cgi-bin/message/send?access_token={token}"
        
        # 构建消息体
        message = {
            "touser": "@all",
            "msgtype": msgtype,
            "agentid": self.agentid,
        }
        
        if msgtype == "text":
            message["text"] = {"content": content}
        elif msgtype == "markdown":
            message["markdown"] = {"content": content}
        
        try:
            response = requests.post(url, json=message, timeout=10)
            response.raise_for_status()
            data = response.json()
            
            if data.get("errcode") == 0:
                print("消息发送成功")
                return True
            else:
                print(f"消息发送失败: {data.get('errmsg')}")
                return False
                
        except Exception as e:
            print(f"发送消息时发生错误: {e}")
            return False

class HotcoinAPI:
    """Hotcoin交易所API客户端"""
    
    def __init__(self, base_url="https://api.Hotcoinfin.com/v1"):
        self.base_url = base_url
        self.session = requests.Session()
        self.session.headers.update({
            'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36',
            'Accept': 'application/json'
        })
    
    def get_ticker(self, symbol):
        """
        获取指定交易对象的行情数据
        
        Args:
            symbol: 交易对象符号，如 btc_usdt, eth_usdt
            
        Returns:
            dict: 行情数据字典，失败返回None
        """
        url = f"{self.base_url}/market/ticker"
        params = {"symbol": symbol}
        
        try:
            response = self.session.get(url, params=params, timeout=10)
            response.raise_for_status()
            
            data = response.json()
            
            if data.get("status") != "ok":
                print(f"API返回错误状态: {data.get('status')}")
                return None
            
            # 解析嵌套的数据结构
            ticker_list = data.get("ticker", [])
            if not ticker_list:
                print(f"未找到 {symbol} 的ticker数据")
                return None
            
            # 第一层ticker
            outer_ticker = ticker_list[0]
            
            # 第二层ticker
            inner_ticker_list = outer_ticker.get("ticker", [])
            if not inner_ticker_list:
                print(f"未找到 {symbol} 的内部ticker数据")
                return None
            
            # 实际的行情数据
            ticker_data = inner_ticker_list[0]
            
            return {
                "raw_data": data,
                "ticker": ticker_data,
                "timestamp": data.get("timestamp")
            }
            
        except requests.exceptions.Timeout:
            print(f"请求 {symbol} 超时，请检查网络连接")
            return None
        except requests.exceptions.ConnectionError:
            print(f"请求 {symbol} 网络连接错误，请检查网络设置")
            return None
        except requests.exceptions.HTTPError as e:
            print(f"请求 {symbol} HTTP错误: {e}")
            return None
        except json.JSONDecodeError as e:
            print(f"请求 {symbol} JSON解析错误: {e}")
            return None
        except Exception as e:
            print(f"请求 {symbol} 未知错误: {e}")
            return None
    
    def safe_float_convert(self, value, default=0.0):
        """安全地将值转换为浮点数"""
        if value is None:
            return default
        try:
            return float(value)
        except (ValueError, TypeError):
            return default
    
    def format_price(self, price_str, decimal_places=2):
        """格式化价格显示"""
        price = self.safe_float_convert(price_str)
        if price == 0.0 and price_str != "0" and price_str != "0.0":
            return "N/A"
        return f"${price:,.{decimal_places}f}"
    
    def format_volume(self, volume_str, decimal_places=4):
        """格式化成交量显示"""
        volume = self.safe_float_convert(volume_str)
        if volume == 0.0 and volume_str != "0" and volume_str != "0.0":
            return "N/A"
        return f"{volume:,.{decimal_places}f}"
    
    def format_change(self, change_str):
        """格式化涨跌幅显示"""
        try:
            change_value = float(change_str) if change_str is not None else 0
            return change_value
        except:
            return 0
    
    def format_ticker_for_wecom(self, ticker_data, symbol):
        """格式化行情数据为企业微信消息（纯文本格式）"""
        if not ticker_data:
            return f"❌ 无法获取 {symbol.upper()} 的行情数据"
        
        ticker = ticker_data["ticker"]
        timestamp = ticker_data["timestamp"]
        
        # 格式化时间
        if timestamp:
            dt = datetime.fromtimestamp(timestamp)
            formatted_time = dt.strftime("%Y-%m-%d %H:%M:%S")
        else:
            formatted_time = "未知时间"
        
        # 获取涨跌幅
        change_value = self.format_change(ticker.get("change"))
        
        # 构建纯文本格式消息
        message = f"🔥 Hotcoin {symbol.upper()} 行情数据 - {formatted_time}\n\n"
        message += f"交易对象: {ticker.get('symbol', symbol).upper()}\n"
        message += f"最新价格: {self.format_price(ticker.get('last'))}\n"
        message += f"买入价: {self.format_price(ticker.get('buy'))}\n"
        message += f"卖出价: {self.format_price(ticker.get('sell'))}\n"
        message += f"24小时最高: {self.format_price(ticker.get('high'))}\n"
        message += f"24小时最低: {self.format_price(ticker.get('low'))}\n"
        message += f"24小时成交量: {self.format_volume(ticker.get('vol'))} {symbol.split('_')[0].upper()}\n"
        message += f"24小时涨跌幅: {change_value}% {'📈' if change_value >= 0 else '📉'}\n"
        
        # 计算买卖价差
        try:
            buy_price = self.safe_float_convert(ticker.get('buy'))
            sell_price = self.safe_float_convert(ticker.get('sell'))
            if buy_price > 0 and sell_price > 0:
                spread = sell_price - buy_price
                spread_percent = (spread / buy_price) * 100
                message += f"买卖价差: ${spread:.2f} ({spread_percent:.4f}%)"
        except:
            pass
        
        return message

def get_symbols_from_env():
    """
    从环境变量Hotcoin中获取交易对象列表
    支持多交易对象用换行分隔
    """
    env_value = os.getenv('Hotcoin', '').strip()
    
    if not env_value:
        print("⚠️  未找到环境变量 Hotcoin，使用默认交易对象")
        return ["btc_usdt", "eth_usdt", "doge_usdt"]
    
    # 按换行符分割，并过滤空行和前后空格
    symbols = [s.strip() for s in env_value.split('\n') if s.strip()]
    
    # 验证交易对象格式（简单验证）
    valid_symbols = []
    for symbol in symbols:
        if '_' in symbol and len(symbol.split('_')) == 2:
            valid_symbols.append(symbol)
        else:
            print(f"⚠️  跳过格式无效的交易对象: {symbol}")
    
    if not valid_symbols:
        print("⚠️  环境变量 Hotcoin 中没有有效的交易对象，使用默认交易对象")
        return ["btc_usdt", "eth_usdt", "doge_usdt"]
    
    print(f"✅ 从环境变量加载了 {len(valid_symbols)} 个交易对象")
    return valid_symbols

def main():
    """主函数"""
    # 初始化API客户端和企业微信机器人
    api = HotcoinAPI()
    
    # 企业微信配置
    corpid = "ww2180cf50a316a275"
    corpsecret = "PPPV0BmRWrV72htwSjjfXpboEVaSK1lItQ9VHmCiWiM"
    agentid = 1000002
    
    wecom_bot = WeComBot(corpid, corpsecret, agentid)
    
    print("🔥 Hotcoin 多币种行情查询工具 - 企业微信推送")
    print("=" * 50)
    
    # 从环境变量获取交易对象列表
    symbols = get_symbols_from_env()
    print(f"📊 将查询的交易对象: {', '.join(symbols)}")
    
    # 成功发送的消息计数
    success_count = 0
    
    for i, symbol in enumerate(symbols):
        print(f"\n[{i+1}/{len(symbols)}] 正在查询 {symbol.upper()} 行情...")
        
        # 查询行情数据
        data = api.get_ticker(symbol)
        message = api.format_ticker_for_wecom(data, symbol)
        
        # 打印到控制台
        print(message)
        
        # 单独发送每条消息到企业微信
        print(f"正在推送 {symbol.upper()} 行情到企业微信...")
        success = wecom_bot.send_message(message, "text")
        
        if success:
            success_count += 1
            print(f"✅ {symbol.upper()} 行情推送成功")
        else:
            print(f"❌ {symbol.upper()} 行情推送失败")
        
        # 如果不是最后一个交易对象，则等待5秒（避免发送频率过高）
        if i < len(symbols) - 1:
            print(f"⏳ 等待5秒后查询下一个交易对象...")
            time.sleep(5)
    
    # 汇总结果
    print(f"\n" + "="*50)
    print(f"📋 任务完成汇总:")
    print(f"   总交易对象数量: {len(symbols)}")
    print(f"   成功推送数量: {success_count}")
    print(f"   失败数量: {len(symbols) - success_count}")
    
    if success_count == len(symbols):
        print("🎉 所有交易对象行情均已成功推送到企业微信！")
    else:
        print("⚠️  部分交易对象行情推送失败，请检查日志")

if __name__ == "__main__":
    try:
        main()
    except KeyboardInterrupt:
        print("\n\n程序已退出")
    except Exception as e:
        print(f"程序运行错误: {e}")
        sys.exit(1)